package math.vectorSpace.R2;

import gravity.Gravity_Simulator_1D;

import java.applet.Applet;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Image;
import java.awt.geom.Ellipse2D;
import java.awt.geom.Rectangle2D;

/**
 * The Draw2D class. Any Simulation that wishes to be drawn in 2D should use this class.
 * Note, any 3D Simulation that wishes to be drawn to the screen should use Draw3D instead.
 * 
 * @author Shimu Wu
 */

public class Draw2D extends Applet implements Runnable {

	private static final long serialVersionUID = 1L;

	// ----------------- These constants can be changed --------------
	private final static int SCREENX = 800;
	private final static int SCREENY = 700;

	private final static double X_AXIS_LEN = 900;
	private final static double Y_AXIS_LEN = 1200;
	// ---------------------------------------------------------------

	// ---------------- DO NOT MODIFY THESE CONSTANTS ----------------

	protected final static double magnification = 0.4;
	// Math.min(SCREENX, SCREENY)/ Math.max(Math.max(X_AXIS_LEN, Y_AXIS_LEN), Z_AXIS_LEN);

	protected final static Vector2D XAXIS = new Vector2D(X_AXIS_LEN / 2.0, 0);
	protected final static Vector2D YAXIS = new Vector2D(0, Y_AXIS_LEN / 2.0);
	// ---------------------------------------------------------------

	private Image screenBuffer;
	private Graphics2D sG;
	private Gravity_Simulator_1D simulator;
	private Rectangle2D background = new Rectangle2D.Double(0, 0, SCREENX, SCREENY);
	private Color backColor = new Color(1.0f, 1.0f, 1.0f);
	
	@Override
	public void init() {
		setSize(SCREENX, SCREENY);
		screenBuffer = createImage(SCREENX, SCREENY);
		sG = (Graphics2D) screenBuffer.getGraphics();

		simulator = new Gravity_Simulator_1D(10, SCREENX);
		simulator.initialize();
		System.out.println("Applet began! :D");
	}

	public void paint(Graphics g) {

		simulator.update();

		sG.setColor(backColor);
		sG.fill(background);
		
		math.vectorSpace.R2.Point2D[] points = simulator.returnPoints();
		Ellipse2D[] ellipses = simulator.returnEllipses();
		
		sG.setColor(new Color (0.0f, 0.0f, 0.0f));
		for (int i = 0; i < points.length; i++) {
			sG.fill(new Ellipse2D.Double(points[i].getX(), points[i].getY(), 2,
					2));
		}

		for (int i = 0; i < ellipses.length; i++) {
			sG.fill(ellipses[i]);
		}
		
		g.drawImage(screenBuffer, 0, 0, this);
	}

	// copied and pasted from a source
	// used as a delay
	protected static void delay(int ms) {
		try {
			Thread.sleep(ms);
		} catch (Exception e) {
			;
		}
	}

	private Thread runner;

	@Override
	public void start() {
		if (runner == null) {
			runner = new Thread(this);
			runner.start();
		}
	}

	public void run() {
		int delayTime = 10;
		long startTime;

		while (true) {
			// starts timing
			startTime = System.currentTimeMillis();
			repaint();

			System.out.println((System.currentTimeMillis() - startTime));
			// Subtracts the time it took to execute the code 
			// away from the delay time

			delay((int) (delayTime - (System.currentTimeMillis() - startTime)));
		}
	}

	@Override
	public void update(Graphics g) {
		paint(g);
	}

}
